﻿/**************************************************************
 *
 * 唯一标识：f7a9d210-3eaf-4a55-99e8-45fabef81954
 * 命名空间：Sgr.DepartmentAggregate
 * 创建时间：2023/8/6 11:56:33
 * 机器名称：DESKTOP-S0D075D
 * 创建者：antho
 * 电子邮箱：fengqinhua2016@163.com
 * 描述：
 *
 **************************************************************/

using Sgr.Domain.Entities;
using Sgr.Domain.Entities.Auditing;
using Sgr.Exceptions;
using Sgr.Generator;
using Sgr.UPMS.Events;
using System.Xml.Linq;

namespace Sgr.UPMS.Domain.Departments
{
    /// <summary>
    /// 部门
    /// </summary>
    public class Department : CreationAndModifyAuditedEntity<long, long>, IAggregateRoot, IOptimisticLock, IMustHaveOrg<long>, ITreeNode<long>, IHaveCode
    {
        private Department()
        {
            State = EntityStates.Normal;
        }

        public Department(string code, string name, int orderNumber, string? remarks, long orgId)
        {
            Code = code;
            Name = name;
            OrderNumber = orderNumber;
            Remarks = remarks;
            OrgId = orgId;
        }

        /// <summary>
        /// 部门编码
        /// </summary>
        public string Code { get; set; } = string.Empty;

        /// <summary>
        /// 部门名称
        /// </summary>
        public string Name { get; private set; } = string.Empty;

        /// <summary>
        /// 排序号
        /// </summary>
        public int OrderNumber { get; set; } = 0;

        /// <summary>
        /// 主管用户Id
        /// </summary>
        public long? ManagerUserId { get; private set; }

        /// <summary>
        /// 负责人/联系人
        /// </summary>
        public string? Leader { get; private set; }

        /// <summary>
        /// 联系电话
        /// </summary>
        public string? Phone { get; private set; }

        /// <summary>
        /// 联系邮箱
        /// </summary>
        public string? Email { get; private set; }

        /// <summary>
        /// 备注
        /// </summary>
        public string? Remarks { get; set; }

        /// <summary>
        /// 部门状态
        /// </summary>
        public EntityStates State { get; private set; } = EntityStates.Normal;

        #region 修改

        /// <summary>
        /// 修改部门名称
        /// </summary>
        /// <param name="name"></param>
        public void ChangeName(string name)
        {
            Name = name;
        }

        public void ChangeManagerUser(long? managerUserId, string? leader, string? phone, string? email)
        {
            Leader = leader;
            Phone = phone;
            Email = email;

            if (ManagerUserId != managerUserId)
            {
                ManagerUserId = managerUserId;

                this.AddDomainEvent(new DepartmentManagerUserChangedDomainEvent(this.Id, this.OrgId, this.ManagerUserId));
            }
        }

        #endregion 修改

        #region 状态管理

        /// <summary>
        /// 修改状态
        /// </summary>
        /// <param name="state">状态</param>
        internal void ChangeState(EntityStates state)
        {
            if (State != state)
            {
                State = state;
            }
        }

        /// <summary>
        /// 标记删除
        /// </summary>
        public void MarkAsDeleted()
        {
            //State = EntityStates.Deactivate;
            MarkAsChanged();
        }

        /// <summary>
        /// 标记发生改变
        /// </summary>
        public void MarkAsChanged()
        {
            this.AddDomainEvent(new DepartmentChangedDomainEvent(this.Id, this.OrgId));
        }

        /// <summary>
        /// 恢复启用
        /// </summary>
        public void Restore()
        {
            if (State == EntityStates.Deactivate)
            {
                State = EntityStates.Normal;
            }
        }

        #endregion 状态管理

        #region ITreeNode (树形结构)

        /// <summary>
        /// 改变父
        /// </summary>
        /// <param name="parentId"></param>
        /// <param name="nodePath"></param>
        internal void SetParent(long parentId, string nodePath)
        {
            if (ParentId != parentId)
            {
                this.ParentId = parentId;
            }
            this.NodePath = nodePath;
        }

        /// <summary>
        /// 上级组织Id
        /// </summary>
        public long ParentId { get; private set; } = 0;

        /// <summary>
        /// 树节点层次目录
        /// </summary>
        public string NodePath { get; private set; } = string.Empty;

        #endregion ITreeNode (树形结构)

        #region IOptimisticLock (乐观锁)

        /// <summary>
        /// 行版本
        /// </summary>
        public long RowVersion { get; set; }

        #endregion IOptimisticLock (乐观锁)

        #region IMustHaveOrg  (如果一个实体实现该接口，那么必须存储实体所在组织的ID.)

        /// <summary>
        /// 所属组织
        /// </summary>
        public long OrgId { get; internal protected set; }

        #endregion IMustHaveOrg  (如果一个实体实现该接口，那么必须存储实体所在组织的ID.)
    }
}